﻿// CheckProjectRadiationRunDialog.cpp: 实现文件
//

#include "stdafx.h"
#include "zChecker.h"
#include "CheckProjectRadiationRunDialog.h"
#include "afxdialogex.h"

#include "MainFrm.h"


UINT project_radiation_compute_proc(LPVOID pParam)
{
	CCheckProjectRadiationRunDialog* pDialog = (CCheckProjectRadiationRunDialog*)pParam;
	pDialog->Run();

	return 0;
}

// CCheckProjectRadiationRunDialog 对话框

IMPLEMENT_DYNAMIC(CCheckProjectRadiationRunDialog, CDialogEx)

CCheckProjectRadiationRunDialog::CCheckProjectRadiationRunDialog(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_DIALOG_CHECK_PROJECT_RADIATION_RUN, pParent)
	, m_strProjName(_T(""))
	, m_strDatasetCount(_T(""))
	, m_strOutputPath(_T(""))
{
	m_pProject = NULL; 
	m_pDatasets = NULL;
	m_nCount = 0;
	m_productType = ck::ckDptUnknown;

	m_strOutputPath = "E:\\Temp\\glcm";
}

CCheckProjectRadiationRunDialog::~CCheckProjectRadiationRunDialog()
{

}

void CCheckProjectRadiationRunDialog::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
	DDX_Text(pDX, IDC_EDIT_PROJECT_NAME, m_strProjName);
	DDX_Text(pDX, IDC_EDIT_DATASET_COUNT, m_strDatasetCount);
	DDX_Text(pDX, IDC_EDIT_OUTPUT_PATH, m_strOutputPath);
	DDX_Control(pDX, IDC_PROGRESS1, m_progressBar);
}


BEGIN_MESSAGE_MAP(CCheckProjectRadiationRunDialog, CDialogEx)
	ON_BN_CLICKED(IDOK, &CCheckProjectRadiationRunDialog::OnBnClickedOk)
	ON_BN_CLICKED(IDC_BTN_OUTPUT_PATH, &CCheckProjectRadiationRunDialog::OnBnClickedBtnOutputPath)
	ON_WM_DESTROY()
	ON_BN_CLICKED(IDCANCEL, &CCheckProjectRadiationRunDialog::OnBnClickedCancel)
	ON_MESSAGE(WM_UPDATE_PROJECT_RADIATION_RUN_PROGRESS, &CCheckProjectRadiationRunDialog::OnUpdateProgressCtrl)
END_MESSAGE_MAP()


// CCheckProjectRadiationRunDialog 消息处理程序


BOOL CCheckProjectRadiationRunDialog::OnInitDialog()
{
	CDialogEx::OnInitDialog();

	// TODO:  在此添加额外的初始化
	if (m_pProject)
	{
		m_strProjName = m_pProject->GetName();
		m_nCount = m_pProject->GetDatasetCount();
		CString str;
		str.Format("%d", m_nCount);
		m_strDatasetCount = str;


		UpdateData(FALSE);

		m_progressBar.SetRange(0, m_nCount);
		//m_progressBar.SetRange(0, 10);
		m_progressBar.SetPos(0);
	}
	

	return TRUE;  // return TRUE unless you set the focus to a control
				  // 异常: OCX 属性页应返回 FALSE
}


void CCheckProjectRadiationRunDialog::SetProject(ck::CheckProject *pProject)
{
	m_pProject = pProject;
}



ck::data::LandsatRadiation* CCheckProjectRadiationRunDialog::ComputeRadiation(ck::data::Landsat05* pLandsat)
{
	RESULTCODE rc = RC_SUCCESS;
	ck::data::LandsatRadiation* plr = new ck::data::LandsatRadiation();
	rc = plr->Create(pLandsat);
	if (rc != RC_SUCCESS)
	{
		pLandsat->Release();
		return NULL;
	}

	double cc = pLandsat->ComputeCloudCoverage();
	plr->SetCloudCoverage(cc);

	ck::data::Raster* pRaster = NULL;
	ck::data::RasterBand* pBand = NULL;
	ck::data::RasterRadiation* lsr = plr->GetRadiation();
	ck::data::RasterRadiation* brs = plr->GetBandRadiation();
	ck::data::RasterRadiation* br = NULL;
	z_uint32 nBands = plr->GetBandCount();
	
	//计算每一个波段的辐射参数
	for (z_uint32 i = 0; i < nBands; i++)
	{
		//------------------------------------------------------------------------
		//输出日志
		//------------------------------------------------------------------------
		char szMessage[_MAX_PATH];
		sprintf(szMessage, "\t波段：%s", pLandsat->GetBandName(i));
		CLoggerWriter::GetInstance()->Write(szMessage);

		//------------------------------------------------------------------------
		//执行计算
		//------------------------------------------------------------------------
		pRaster = pLandsat->OpenRaster(i);
		if (pRaster == NULL)
		{
			continue;
		}

		pBand = pRaster->GetBand(0);
		if (pBand)
		{
			ck::processor::raster::RasterBandRadiationProcessor rrp;
			rrp.SetBand(pBand);
			rrp.Execute();
			br = rrp.GetData();

			brs[i] = *br;
			*lsr += *br;
		}

		//*lsr /= nBands;
		pRaster->Release();

	}
	return plr;
}

void CCheckProjectRadiationRunDialog::OnBnClickedOk()
{
	// TODO: 在此添加控件通知处理程序代码
	UpdateData(TRUE);

	CWinThread* pThread = NULL;
	//pThread = AfxBeginThread((AFX_THREADPROC)project_radiation_compute_proc, this, THREAD_PRIORITY_TIME_CRITICAL);
	pThread = AfxBeginThread((AFX_THREADPROC)project_radiation_compute_proc, this);
	DisableControls();

	DWORD dwRet;
	DoEvent();
	do
	{
		dwRet = ::MsgWaitForMultipleObjects(1, &pThread->m_hThread, FALSE, INFINITE, QS_ALLINPUT);
		if (dwRet != WAIT_OBJECT_0)
		{
			DoEvent();
		}
		//else
		//{
		//	AfxMessageBox("here");
		//}
	} while ((dwRet != WAIT_OBJECT_0) && (dwRet != WAIT_FAILED));

	DisableControls();

	//Run();
	
	CLoggerWriter::GetInstance()->Write("计算完成");
	AfxMessageBox("计算完成");

	CDialogEx::OnOK();
}

void CCheckProjectRadiationRunDialog::DoEvent()
{
	MSG msg;
	if (::PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))  //取消息，检索应用程序的消息队列，PM_REMOVE取过之后从消息队列中移除
	{
		//发消息
		::TranslateMessage(&msg);
		::DispatchMessage(&msg);
	}

}


void CCheckProjectRadiationRunDialog::OnBnClickedBtnOutputPath()
{
	// TODO: 在此添加控件通知处理程序代码
	char szPath[MAX_PATH]; //存放选择的目录路径 
	CString str;

	ZeroMemory(szPath, sizeof(szPath));
	BROWSEINFO bi;
	bi.hwndOwner = AfxGetMainWnd()->m_hWnd;
	bi.pidlRoot = NULL;
	bi.pszDisplayName = szPath;
	bi.lpszTitle = "请选择GDB目录";
	bi.ulFlags = 0x0040 | BIF_RETURNONLYFSDIRS | BIF_EDITBOX; ;
	bi.lpfn = NULL;
	bi.lParam = 0;
	bi.iImage = 0;

	LPITEMIDLIST lp = ::SHBrowseForFolder(&bi);
	if (lp && SHGetPathFromIDList(lp, szPath))
	{
		m_strOutputPath = szPath;
		UpdateData(FALSE);
	}

}



void CCheckProjectRadiationRunDialog::OnDestroy()
{
	CDialogEx::OnDestroy();

	// TODO: 在此处添加消息处理程序代码
	if (m_pDatasets)
	{
		m_pDatasets->Release();
		m_pDatasets = NULL;
	}
}


void CCheckProjectRadiationRunDialog::OnBnClickedCancel()
{
	// TODO: 在此添加控件通知处理程序代码
	//::PostMessage(GetSafeHwnd(), WM_UPDATE_PROJECT_RADIATION_RUN_PROGRESS, (WPARAM)3, 0);

	CDialogEx::OnCancel();
}


void CCheckProjectRadiationRunDialog::DisableControls()
{
	GetDlgItem(IDC_EDIT_OUTPUT_PATH)->EnableWindow(FALSE);
	GetDlgItem(IDOK)->EnableWindow(FALSE);
	GetDlgItem(IDCANCEL)->EnableWindow(FALSE);
	GetDlgItem(IDC_BTN_OUTPUT_PATH)->EnableWindow(FALSE);
}

void CCheckProjectRadiationRunDialog::EnableControls()
{
	GetDlgItem(IDC_EDIT_OUTPUT_PATH)->EnableWindow(TRUE);
	GetDlgItem(IDOK)->EnableWindow(TRUE);
	GetDlgItem(IDCANCEL)->EnableWindow(TRUE);
	GetDlgItem(IDC_BTN_OUTPUT_PATH)->EnableWindow(TRUE);
}

LRESULT CCheckProjectRadiationRunDialog::OnUpdateProgressCtrl(WPARAM wParam, LPARAM lParam)
{
	int pos = (int)wParam;
	m_progressBar.SetPos(pos);
	return 0;
}


void CCheckProjectRadiationRunDialog::Run()
{
	ck::DataSource* pDataSource = NULL;
	ck::EnumDataSource* pDataSources = NULL;	
	ck::CheckProject* pProject = m_pProject;

	AfxGetMainWnd()->BeginWaitCursor();

	//获取数据产品类型
	ck::ckDataProductType productType = pProject->GetProductType();

	//更新进度条
	//pDialog->m_progressBar.SetPos(1);
	::PostMessage(GetSafeHwnd(), WM_UPDATE_PROJECT_RADIATION_RUN_PROGRESS, (WPARAM)1, 0);

	//遍历工程的DataSource
	int index = 0;
	pDataSources = pProject->GetDataSources();
	pDataSources->Reset();
	while ((pDataSource = pDataSources->Next()))
	{
		//遍历每个DataSource的Dataset
		ck::data::Dataset* pDataset = NULL;
		ck::data::EnumDataset* pDatasets = NULL;
		pDatasets = pDataSource->GetDatasets(productType);
		pDatasets->Reset();
		while ((pDataset = pDatasets->Next()))
		{
			ck::data::Landsat05* pLandsat05 = (ck::data::Landsat05*)pDataset;
			pLandsat05->Open();
			index++;

			TRACE1("%s\n", pLandsat05->GetName());

			//------------------------------------------------------------------------
			//写日志
			//------------------------------------------------------------------------
			char szDataSetPath[_MAX_PATH];
			memset(szDataSetPath, 0, _MAX_PATH);
			strcpy(szDataSetPath, pLandsat05->GetPath());
			CLoggerWriter::GetInstance()->Write(szDataSetPath);

			//------------------------------------------------------------------------
			//计算辐射参数
			//------------------------------------------------------------------------
			ck::data::LandsatRadiation* lr = ComputeRadiation(pLandsat05);
			if (lr != NULL)
			{
				//写文件
				char szOutFilePath[_MAX_PATH];
				memset(szOutFilePath, 0, _MAX_PATH);
				_makepath(szOutFilePath, NULL, m_strOutputPath, pLandsat05->GetName(), "txt");
				//const char* szProjOutPath = "E:\\Temp\\glcm\\";
				//_makepath(szOutFilePath, NULL, szProjOutPath, pLandsat05->GetName(), "txt");
				lr->Write(szOutFilePath);
				lr->Release();
			}
			//pDialog->m_progressBar.SetPos(index);
			//更新进度条
			//pDialog->m_progressBar.SetPos(1);
			::PostMessage(GetSafeHwnd(), WM_UPDATE_PROJECT_RADIATION_RUN_PROGRESS, (WPARAM)index, 0);
		}

		pDatasets->Release();
	}
	pDataSources->Release();

	AfxGetMainWnd()->EndWaitCursor();
}
